package com.medium.house.utils;

import com.fasterxml.jackson.core.JsonGenerationException;
import com.fasterxml.jackson.core.JsonGenerator;
import com.fasterxml.jackson.core.JsonParseException;
import com.fasterxml.jackson.databind.ObjectMapper;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import java.io.IOException;
import java.io.InputStream;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

public class JacksonUtils {
	private static final Logger logger = LoggerFactory.getLogger(JacksonUtils.class);
	private static final ObjectMapper mapper = createObjectMapper();

	/*private Map<String, Object> data = new HashMap<String, Object>();
	public void addObject(String key, Object value){data.put(key, value);}
	private JacksonUtils() {}
	public  String jsonEncode()
	{
		return JacksonUtils.compressMap(data);
	}*/

	private static ObjectMapper createObjectMapper() {
		ObjectMapper objectMapper = new ObjectMapper();
		objectMapper.configure(JsonGenerator.Feature.AUTO_CLOSE_TARGET, false);
		return objectMapper;
	}

	public static ObjectMapper getMapper() {
		return mapper;
	}

	/**
	 * 当需要屏蔽结果的对象中某些字段时, 需要用特定的view去过滤
	 *
	 * @param o 待序列化的实例, 可以是list, map或者某个对象
	 * @param clazz 自己定义的jackson view对象
	 * @return 序列化后产生的字符串
	 */
	public static String compressByView(Object o, Class<?> clazz) {
		try {
			return mapper.writerWithView(clazz).writeValueAsString(o);
		} catch (JsonGenerationException e) {
			logger.error("JsonGenerationException");
			logger.debug(e.getMessage(), e);
			return null;
		} catch (IOException e) {
			logger.error("compressByView IOException");
			logger.debug(e.getMessage(), e);
			return null;
		}
	}

	public static <T> T extractObject(String json, Class<T> valueType) {
		if (json == null || json.equals("")) {return null;}
		T output = null;
		try {
			output = mapper.readValue(json, valueType);
		} catch (JsonParseException e) {
			logger.error("JsonParseException");
			logger.debug(e.getMessage(), e);
		} catch (IOException e) {
			logger.error("extractObject IOException");
			logger.debug(e.getMessage(), e);
		}
		return output;
	}

	public static <T> T extractObject(InputStream is, Class<T> valueType) {
		if (is == null) {return null;}
		T output = null;
		try {
			output = mapper.readValue(is, valueType);
		} catch (JsonParseException e) {
			logger.error("JsonParseException");
			logger.debug(e.getMessage(), e);
		} catch (IOException e) {
			logger.error("extractObject IOException");
			logger.debug(e.getMessage(), e);
		}
		return output;
	}

	public static <T> String compressObject(T object) {
		String json = "";
		try {
			json = mapper.writeValueAsString(object);
		} catch (JsonGenerationException e) {
			logger.error("JsonGenerationException");
			logger.debug(e.getMessage(), e);
		} catch (IOException e) {
			logger.error("compressObject IOException");
			logger.debug(e.getMessage(), e);
		}
		return json;
	}

	public static <T> List<T> extractList(String listString, List<T> list) {
		if (listString == null || listString.length() == 0) {return list;}
		List<T> output = null;
		try {
			output = mapper.readValue(listString, list.getClass());
		} catch (JsonParseException e) {
			logger.error("JsonParseException");
			logger.debug(e.getMessage(), e);
		} catch (IOException e) {
			logger.error("extractList IOException");
			logger.debug(e.getMessage(), e);
		}
		return (output == null) ? list : output;
	}

	public static <T> String compressList(List<T> list) {
		String listString = "";
		try {
			listString = mapper.writeValueAsString(list);
		} catch (JsonGenerationException e) {
			logger.error("JsonGenerationException");
			logger.debug(e.getMessage(), e);
		} catch (IOException e) {
			logger.error("compressList IOException");
			logger.debug(e.getMessage(), e);
		}
		return listString;
	}

	public static <T, S> Map<T, S> extractMap(String mapString, Map<T, S> map) {
		if (mapString == null || mapString.equals("")) {return map;}
		Map<T, S> output = null;
		try {
			output = mapper.readValue(mapString, map.getClass());
		} catch (JsonParseException e) {
			logger.error("JsonParseException");
			logger.debug(e.getMessage(), e);
		} catch (IOException e) {
			logger.error("extractMap IOException");
			logger.debug(e.getMessage(), e);
		}
		return (output == null) ? map : output;
	}

	public static <T, S> String compressMap(Map<T, S> map) {
		String mapString = "";
		try {
			mapString = mapper.writeValueAsString(map);
		} catch (JsonGenerationException e) {
			logger.error("JsonGenerationException");
			logger.debug(e.getMessage(), e);
		} catch (IOException e) {
			logger.error("compressMap IOException");
			logger.debug(e.getMessage(), e);
		}
		return mapString;
	}

	public static void main(String[] args) {
		Map<String, String> map = new HashMap<String, String>();
		ArrayList< String> al = new ArrayList<String>();
		al.add("123123");
		al.add("5555");
		String output2  = compressList(al);
		map.put("html_content", "1");
		map.put("css_content", "2");
		String output = compressMap(map);
		System.out.println(output2);

		/*
		Menu menu = new Menu();
		Button button1 = new Button("click", "歌曲", "V1001_TODAY_MUSIC", null, null);
		Button button2 = new Button("click", "歌曲", null, "http://www.abc.com", null);
		Button button3 = new Button("click", "歌曲", "bbt108193", null, null);
		List<Button> btns = new ArrayList<>();
		btns.add(button1);
		btns.add(button2);
		btns.add(button3);
		Button button4 = new Button(null, "菜单", null, null, btns);
		menu.addButton(button1);
		menu.addButton(button2);
		menu.addButton(button4);
		System.out.println(compressObject(menu));*/

	}
}
